<template>
  <Form ref="formValidate" :style="{ width: width > 0 ? width + 'px' : '100%' }" :model="_formFields" :label-width="labelWidth" @submit.native.prevent>
    <!-- :rules="ruleValidate" -->
    <slot name="header"></slot>
    <Row class="line-row" v-for="(row, findex) in formRules" :key="findex">
      <!-- 2020.11.21增加表单hidden属性 -->
      <Col :span="item.colSize ? item.colSize * 2 : 24 / span" v-for="(item, index) in row" :key="index" v-show="!item.hidden">

      <form-expand v-if="item.render && typeof item.render == 'function'" :render="item.render"></form-expand>
      <Row class="line-row" v-else-if="item.collist" v-for="(colrow, colindex) in item.collist" :key="colindex">
        <!-- 2020.11.21增加表单hidden属性 -->
        <Col :span="colrowitem.colSize ? colrowitem.colSize * 2 : 24 / span" v-for="(colrowitem, colrowindex) in colrow" :key="colrowindex" v-show="!colrowitem.hidden">
        <!-- 2020.06.18增加render渲染自定义内容 -->
        <form-expand v-if="colrowitem.render && typeof colrowitem.render == 'function'" :render="colrowitem.render"></form-expand>
        <template v-else :rules="getRule(colrowitem, _formFields)" :label="colrowitem.title ? colrowitem.title + '：' : ''" :label-width="colrowitem.width" :prop="colrowitem.field">
          <div v-if="isReadonlyImgFile(colrowitem, _formFields)">
            <div v-if="
                    colrowitem.type == 'img' || colrowitem.columnType == 'img'
                  " class="form-imgs">
              <div class="img-item" v-for="(img, imgIndex) in _formFields[colrowitem.field]" :key="imgIndex">
                <img :src="getSrc(img.path)" :onerror="errorImg" @click="previewImg(img.path)" />
              </div>
            </div>
            <div v-else>
              <div class="form-file-list" v-for="(file, fileIndex) in _formFields[colrowitem.field]" :key="fileIndex">
                <a @click="
                        dowloadFile(_formFields[colrowitem.field][fileIndex])
                      ">{{ file.name }}</a>
              </div>
            </div>
          </div>
          <div v-else :class="{ 'form-item-extra': colrowitem.extra }">
            <label v-if="colrowitem.disabled || colrowitem.readonly" class="readonly-input">{{ getText(_formFields, colrowitem) }}</label>
            <!--下拉框绑定时如果key为数字，请将key+''转换为字符串-->
            <template v-else-if="
                    colrowitem.type == 'select' ||
                    colrowitem.type == 'selectList' ||
                    colrowitem.type == 'drop' ||
                    colrowitem.type == 'dropList'
                  ">
              <!--select绑定默认值时，如果设置了默认值，数据源也有数据，但没绑定上，问题在于key与默认值类型不一致，如:默认值是字符串，数据源的key是数字，类型不至会导致绑定失败-->
          </template>
                <!-- {{ item.remote||item.url?"1":"0"}} -->
                <!-- 远程搜索 -->
                <!-- 从后台字典搜索remote  -->
                <Select v-if="colrowitem.remote || colrowitem.url" :transfer="true" v-model="_formFields[colrowitem.field]" filterable remote @on-clear="
                        () => {
                          onClear(colrowitem, _formFields);
                        }
                      " :remote-method="
                        (val) => {
                          remoteSearch(colrowitem, _formFields, val);
                        }
                      " :loading="colrowitem.loading" :placeholder="
                        colrowitem.placeholder
                          ? colrowitem.placeholder
                          : '请选择' + colrowitem.title
                      " @on-change="
                        onRemoteChange(
                          colrowitem,
                          _formFields[colrowitem.field]
                        )
                      " clearable>
                  <Option v-for="(kv, kvIndex) in getData(colrowitem)" :key="kvIndex" :value="kv.key">{{ kv.value }}</Option>
                </Select>
                <Select v-else :transfer="true" v-model="_formFields[colrowitem.field]" :multiple="
                        colrowitem.type == 'select' || colrowitem.type == 'drop'
                          ? false
                          : true
                      " :filterable="
                        colrowitem.filter || colrowitem.data.length > 10
                          ? true
                          : false
                      " :placeholder="
                        colrowitem.placeholder
                          ? colrowitem.placeholder
                          : '请选择' + colrowitem.title
                      " @on-change="onChange(item, _formFields[colrowitem.field])" clearable>
                  <Option v-for="(kv, kvIndex) in colrowitem.data" :key="kvIndex" :value="kv.key" v-show="!kv.hidden">{{ kv.value }}</Option>
                </Select>
          </div>
        </template>
            <i-switch v-else-if="colrowitem.type == 'switch'" :true-value="
                    typeof _formFields[colrowitem.field] == 'boolean' ? true : 1
                  " :false-value="
                    typeof _formFields[colrowitem.field] == 'boolean'
                      ? false
                      : 0
                  " v-model="_formFields[colrowitem.field]" @on-change="
                    onChange(colrowitem, _formFields[colrowitem.field])
                  ">
              <span slot="open">{{ colrowitem.textSpan ? colrowitem.textSpan[0] : '是' }}</span>
              <span slot="close">{{ colrowitem.textSpan ? colrowitem.textSpan[1] : '否' }}</span>
            </i-switch>
            <!-- 2021.05.16集成iview radio组件 -->
            <RadioGroup v-else-if="colrowitem.type == 'radio'" v-model="_formFields[colrowitem.field]">
              <Radio :label="kv.key" v-for="(kv, kvIndex) in colrowitem.data" :key="kvIndex">
                <span>{{ kv.value }}</span>
              </Radio>
            </RadioGroup>
            <Row v-else-if="
                    colrowitem.type == 'date' ||
                    colrowitem.type == 'datetime' ||
                    colrowitem.columnType == 'datetime' ||
                    colrowitem.type == 'month'
                  ">
              <Col span="24">
              <FormItem :prop="colrowitem.field">
                <DatePicker :transfer="true" :type="
                          colrowitem.range && colrowitem.type != 'month'
                            ? colrowitem.type + 'range'
                            : colrowitem.type
                        " :format="getDateFormat(colrowitem)" :placeholder="
                          colrowitem.placeholder || '请选择' + colrowitem.title
                        " :value="_formFields[colrowitem.field]" :options="getDateOptions(colrowitem)" @on-change="
                          (time) => {
                            _formFields[colrowitem.field] = time;
                            validateField(item);
                            return time;
                          }
                        "></DatePicker>
              </FormItem>
              </Col>
            </Row>
            <!-- 2020.10.17增加iview time组件 -->
            <TimePicker confirm v-else-if="colrowitem.type == 'time'" type="time" :format="colrowitem.format" v-model="_formFields[colrowitem.field]"
              :placeholder="colrowitem.placeholder || colrowitem.title">
            </TimePicker>
            <CheckboxGroup @on-change="
                    (arr) => {
                      colrowitem.onChange && colrowitem.onChange(arr);
                    }
                  " v-else-if="colrowitem.type == 'checkbox'" v-model="_formFields[colrowitem.field]">
              <Checkbox v-for="(kv, kvIndex) in colrowitem.data" :key="kvIndex" :label="kv.key">{{ kv.value }}</Checkbox>
            </CheckboxGroup>

            <vol-upload v-else-if="isFile(colrowitem, _formFields)" :desc="colrowitem.desc" :multiple="colrowitem.multiple" :max-file="colrowitem.maxFile"
              :max-size="colrowitem.maxSize" :autoUpload="colrowitem.autoUpload" :fileInfo="_formFields[colrowitem.field]" :url="colrowitem.url" :img="
                    colrowitem.type == 'img' || colrowitem.columnType == 'img'
                  "  :storage="colrowitem.storage" :excel="colrowitem.type == 'excel'" :fileTypes="colrowitem.fileTypes ? colrowitem.fileTypes : []" :upload-before="colrowitem.uploadBefore"
              :upload-after="colrowitem.uploadAfter" :append="colrowitem.multiple" :on-change="colrowitem.onChange" :file-click="colrowitem.fileClick"
              :remove-before="colrowitem.removeBefore" :downLoad="colrowitem.downLoad ? true : false" ></vol-upload>
            <!-- 增加图片库 -->
            <VolUploadUpgrade v-else-if="colrowitem.type == 'imgupgrade'" :img="colrowitem.type == 'imgupgrade' || colrowitem.columnType == 'imgupgrade'" ></VolUploadUpgrade>
            <!-- 2020.05.31增加iview组件Cascader -->
            <!--2020.09.19增加级联 @on-change="item.onChange"事件 -->
            <!--2020.10.23增加级联 change-on-select属性 -->
            <Cascader v-else-if="colrowitem.type == 'cascader'" :load-data="colrowitem.loadData" @on-change="
                    (value, selectedData) => {
                      colrowitem.onChange &&
                        colrowitem.onChange(value, selectedData);
                    }
                  " :ref="colrowitem.field" :change-on-select="colrowitem.changeOnSelect" :data="colrowitem.data" :render-format="colrowitem.formatter" filterable
              v-model="_formFields[colrowitem.field]"></Cascader>
            <kind-editor ref="editor" v-else-if="colrowitem.type == 'editor'" :UploadImgUrl="editor.uploadImgUrl" :upload="editor.upload"
              :content.sync="_formFields[colrowitem.field]" height="460px"></kind-editor>
            <!-- 2021.05.02增加区间查询 -->
            <div style="display: flex" v-else-if="colrowitem.type == 'range' || colrowitem.range">
              <Input style="flex: 1" v-model="_formFields[colrowitem.field][0]" clearable />
              <span style="margin: 0 5px">-</span>
              <Input style="flex: 1" v-model="_formFields[colrowitem.field][1]" clearable />
            </div>
            <!--2020.09.05增加textarea标签的最小高度item.minRows属性 -->
            <Input v-else-if="colrowitem.type == 'textarea'" v-model="_formFields[colrowitem.field]" type="textarea" :show-word-limit='item.showWordLimit' :maxlength='item.maxlength' @on-keypress="
                    ($event) => {
                      colrowitem.onKeyPress && colrowitem.onKeyPress($event);
                    }
                  " clearable :autosize="{
                    minRows: colrowitem.minRows || 2,
                    maxRows: colrowitem.maxRows || 10,
                  }" :placeholder="
                    colrowitem.placeholder
                      ? colrowitem.placeholder
                      : '请输入' + colrowitem.title
                  " :ref="colrowitem.field" />
            <Input clearable v-else-if="colrowitem.type == 'password'" type="password" autocomplete="off" v-model.number="_formFields[colrowitem.field]" @on-keypress="
                    ($event) => {
                      colrowitem.onKeyPress && colrowitem.onKeyPress($event);
                    }
                  " :placeholder="
                    colrowitem.placeholder
                      ? colrowitem.placeholder
                      : '请输入' + colrowitem.title
                  " :ref="colrowitem.field" />
            <Input clearable v-else @on-keypress="
                    ($event) => {
                      colrowitem.onKeyPress && colrowitem.onKeyPress($event);
                    }
                  " @input="
                    ($event) => {
                      colrowitem.onInput && colrowitem.onInput($event);
                    }
                  " v-model="_formFields[colrowitem.field]" :placeholder="
                    colrowitem.placeholder
                      ? colrowitem.placeholder
                      : '请输入' + colrowitem.title
                  " :ref="colrowitem.field" />
            <div class="form-extra" v-if="colrowitem.extra">
              <form-expand v-if="colrowitem.extra.render" :render="colrowitem.extra.render"></form-expand>
              <el-tooltip effect="dark" placement="top" v-if="colrowitem.extra.tooltip">
                <div slot="content" v-html="colrowitem.extra.content"></div>
                <i class="el-icon-question" />
              </el-tooltip>
              <a v-else :style="colrowitem.extra.style" @click="
                      () => {
                        colrowitem.extra.click &&
                          colrowitem.extra.click(
                            colrowitem,
                            _formFields[colrowitem.field]
                          );
                      }
                    ">
                <Icon v-if="colrowitem.extra.icon" :type="colrowitem.extra.icon" />
                {{ colrowitem.extra.text }}
              </a>
            </div>
          <!-- </div>
        </FormItem> -->
        </Col>
      </Row>
      <!-- 2020.06.18增加render渲染自定义内容 -->

      <FormItem v-else :rules="getRule(item, _formFields)" :label="item.title ? item.title + '：' : ''" :label-width="item.width" :prop="item.field"  v-show="!item.hidden">
        <template v-if="isReadonlyImgFile(item, _formFields)">
          <div v-if="item.type == 'img' || item.columnType == 'img'" class="form-imgs">
            <div class="img-item" v-for="(img, imgIndex) in _formFields[item.field]" :key="imgIndex">
              <img :src="getSrc(img.path)" :onerror="errorImg" @click="previewImg(img.path)" />
            </div>
          </div>
          <template v-else>
            <div class="form-file-list" v-for="(file, fileIndex) in _formFields[item.field]" :key="fileIndex">
              <a @click="dowloadFile(_formFields[item.field][fileIndex])">{{
                  file.name
                }}</a>
            </div>
          </template>
        </template>
        <div v-else :class="{ 'form-item-extra': item.extra }">
          <div v-if="item.type == 'header'"></div>
          <label v-else-if="item.disabled || item.readonly" class="readonly-input">{{ getText(_formFields, item) }}</label>
          <!--下拉框绑定时如果key为数字，请将key+''转换为字符串-->
          <template v-else-if="
                item.type == 'select' ||
                item.type == 'selectList' ||
                item.type == 'drop' ||
                item.type == 'dropList'
              ">
            <!--select绑定默认值时，如果设置了默认值，数据源也有数据，但没绑定上，问题在于key与默认值类型不一致，如:默认值是字符串，数据源的key是数字，类型不至会导致绑定失败-->
            </template>
              <!-- {{ item.remote||item.url?"1":"0"}} -->
              <!-- 远程搜索 -->
              <!-- 从后台字典搜索remote  -->
              <Select v-if="item.remote || item.url" :transfer="true" v-model="_formFields[item.field]" filterable remote @on-clear="
                    () => {
                      onClear(item, _formFields);
                    }
                  " :remote-method="
                    (val) => {
                      remoteSearch(item, _formFields, val);
                    }
                  " :loading="item.loading" :placeholder="
                    item.placeholder ? item.placeholder : '请选择' + item.title
                  " @on-change="onRemoteChange(item, _formFields[item.field])" clearable>
                <Option v-for="(kv, kvIndex) in getData(item)" :key="kvIndex" :value="kv.key">{{ kv.value }}</Option>
              </Select>
              <Select v-else :transfer="true" v-model="_formFields[item.field]" :multiple="
                    item.type == 'select' || item.type == 'drop' ? false : true
                  " :filterable="
                    item.filter || item.data.length > 10 ? true : false
                  " :placeholder="
                    item.placeholder ? item.placeholder : '请选择' + item.title
                  " @on-change="onChange(item, _formFields[item.field])" :clearable="item.clearable == undefined ?true:item.clearable">
                <Option v-for="(kv, kvIndex) in item.data" :key="kvIndex" :value="kv.key" v-show="!kv.hidden">{{ kv.value }}</Option>
              </Select>
            </template>
          </template>
          <i-switch v-else-if="item.type == 'switch'" :true-value="
                typeof _formFields[item.field] == 'boolean' ? true : 1
              " :false-value="
                typeof _formFields[item.field] == 'boolean' ? false : 0
              " v-model="_formFields[item.field]" @on-change="onChange(item, _formFields[item.field])">
            <span slot="open">{{ item.textSpan ? item.textSpan[0] : '是' }}</span>
            <span slot="close">{{ item.textSpan ? item.textSpan[1] : '否' }}</span>
          </i-switch>
          <!-- 2021.05.16集成iview radio组件 -->
          <RadioGroup @on-change="
                (arr) => {
                  item.onChange && item.onChange(arr, item);
                }
              " v-else-if="item.type == 'radio'" v-model="_formFields[item.field]">
            <Radio :label="kv.key" v-for="(kv, kvIndex) in item.data" :key="kvIndex">
              <span>{{ kv.value }}</span>
            </Radio>
          </RadioGroup>
          <Row v-else-if="
                item.type == 'date' ||
                item.type == 'datetime' ||
                item.columnType == 'datetime' ||
                item.type == 'month'
              ">
            <Col span="24">
            <FormItem :prop="item.field">
              <DatePicker :transfer="true" :type="
                      item.range && item.type != 'month'
                        ? item.type + 'range'
                        : item.type
                    " :format="getDateFormat(item)" :placeholder="item.placeholder || '请选择' + item.title" :value="_formFields[item.field]" :options="getDateOptions(item)"
                @on-change="
                      (time) => {
                        if(time[1].slice(-8) === '00:00:00'){
                          time[1] = time[1].slice(0,-8) + '23:59:59'
                        }
                        _formFields[item.field] = time;
                        validateField(item);
                        return time;
                      }
                    "></DatePicker>
            </FormItem>
            </Col>

          </Row>
          <DatePicker confirm v-else-if="item.type == 'date1'" format="yyyy-MM-dd" type="date" v-model="_formFields[item.field]" :options="getDateOptions(item)"
          :clearable="item.clearable == undefined ? true : item.clearable"  @on-change="(time)=>{ item.onChange ? item.onChange(time) : _formFields[item.field] = time }" :placeholder="item.placeholder || '请选择' + item.title"></DatePicker>
          <TimePicker confirm v-else-if="item.type == 'time'" type="time" :format="item.format" v-model="_formFields[item.field]"
            :placeholder="item.placeholder || '请选择' + item.title">
          </TimePicker>
          <el-input-number  v-else-if="item.type == 'inpNum'" v-model="_formFields[item.field]" :min="item.min" :max="item.max" size="mini" :step="item.step" :step-strictly="item.stepStrictly"
          :controls-position="item.position" :disabled="item.disabled" :precision="item.precision" @change="(num) =>{ item.change ? item.onChange(num) : null} "></el-input-number>
          <!--  -->

          <!-- 时间段 -->
          <TimePicker :transfer="true" format="HH:mm" type="timerange" v-else-if="item.type == 'is-range'" :placeholder="item.placeholder || item.title"
            :value="_formFields[item.field]" @on-change="
                (time) => {
                  _formFields[item.field] = time;

                  // console.log('kkk', time);

                  // scope.row[column.field] = time;
                  // column.onChange && column.onChange(time, column);
                  return time;
                }
              "></TimePicker>
          <CheckboxGroup @on-change="
                (arr) => {
                  item.onChange && item.onChange(arr, item);
                }
              " v-else-if="item.type == 'checkbox'" v-model="_formFields[item.field]">
            <Checkbox v-for="(kv, kvIndex) in item.data" :key="kvIndex" :label="kv.key" :disabled="kv.disabled">{{ kv.value }}</Checkbox>
          </CheckboxGroup>
          <el-transfer v-else-if="item.type == 'transfer'" :titles="item.titles"
          filterable v-model="_formFields[item.field]" :data="item.data" :props="{
                key: 'key',
                label: 'label',
              }">
            <span slot-scope="{ option }">
                <el-tooltip class="item" v-if="option.label.length > 6" effect="dark" :content="option.label" placement="top" >
                  <span>{{ option.label }}</span>
                </el-tooltip>
                <span v-else>{{ option.label }}</span>
              </span>
            </el-transfer>
          <vol-upload v-else-if="isFile(item, _formFields)" :desc="item.desc" :multiple="item.multiple" :max-file="item.maxFile" :max-size="item.maxSize"
            :autoUpload="item.autoUpload" :fileInfo="_formFields[item.field]" :url="item.url" :img="item.type == 'img' || item.columnType == 'img'" :excel="item.type == 'excel'" :storage="item.storage"
            :fileTypes="item.fileTypes ? item.fileTypes : []" :upload-before="item.uploadBefore" :upload-after="item.uploadAfter" :append="item.multiple" :on-change="item.onChange"
            :file-click="item.fileClick" :remove-before="item.removeBefore" :downLoad="item.downLoad ? true : false"></vol-upload>
          <!-- 2020.05.31增加iview组件Cascader -->
          <!--2020.09.19增加级联 @on-change="item.onChange"事件 -->
          <!--2020.10.23增加级联 change-on-select属性 -->
          <!-- 增加图片库 -->
          <VolUploadUpgrade v-else-if="item.type == 'imgupgrade'" :fileInfo="_formFields[item.field]" :multiple="item.multiple" :max-file="item.maxFile" :max-size="item.maxSize"
            :append="item.multiple" :on-change="item.onChange" :downLoad="item.downLoad ? true : false" :formFields="_formFields">
          </VolUploadUpgrade>
          <Cascader v-else-if="item.type == 'cascader'" :load-data="item.loadData" @on-change="
                (value, selectedData) => {
                  if(item.cascaderValue){
                    let play=null
                    play =  changeProducts(value, selectedData,item.data,item.field)
                    if(play){
                      item.onChange && item.onChange(value, selectedData);
                    }
                  }else{
                    item.onChange && item.onChange(value, selectedData);
                  }
                }
              " :ref="item.field" :change-on-select="item.changeOnSelect" :data="item.data" :render-format="item.formatter" filterable v-model="_formFields[item.field]"
            :placeholder="item.placeholder || '请选择' + item.title"></Cascader>
          <!-- <Cascader v-else-if="item.type == 'cascader'" @on-change="(value, selectedData)=>{ changeProducts(value, selectedData,item.data,_formFields[item.field])}"
            :data="item.data" filterable v-model="_formFields[item.field]"></Cascader> -->
            <el-cascader v-else-if="item.type == 'cascaderEl'" size="mini" v-model="_formFields[item.field]" :options="item.data"
            :props="{
              checkStrictly:item.checkStrictly == undefined ? true : item.checkStrictly,
              multiple: item.multiple == undefined ? true : item.multiple,
              emitPath:item.emitPath == undefined ? false : item.emitPath,
              label:item.label || 'typeName',
              value:item.id || 'id',
            }" @change="(value, selectedData)=>{
              item.onChange && item.onChange(value, selectedData);
            }" :clearable="item.clearable == undefined ? true : item.clearable"
            ></el-cascader>
          <kind-editor ref="editor" v-else-if="item.type == 'editor'" :UploadImgUrl="editor.uploadImgUrl" :upload="editor.upload" :content.sync="_formFields[item.field]"
            height="460px"></kind-editor>
          <!-- 2021.05.02增加区间查询 -->
          <div style="display: flex" v-else-if="item.type == 'range' || item.range">
            <Input style="flex: 1" v-model="_formFields[item.field][0]" clearable />
            <span style="margin: 0 5px">-</span>
            <Input style="flex: 1" v-model="_formFields[item.field][1]" clearable />
          </div>
          <!--2020.09.05增加textarea标签的最小高度item.minRows属性 -->
          <Input v-else-if="item.type == 'textarea'" v-model="_formFields[item.field]" type="textarea" :show-word-limit='item.showWordLimit' :maxlength='item.maxlength' @on-keypress="
                ($event) => {
                  item.onKeyPress && item.onKeyPress($event);
                }
              " clearable :autosize="{
                minRows: item.minRows || 2,
                maxRows: item.maxRows || 10,
              }" :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " :ref="item.field" />
          <Input v-else-if="item.type == 'aaaaa'" v-model="_formFields[item.field]" type="textarea" :show-word-limit='item.showWordLimit' :maxlength='item.maxlength' @on-keypress="
                ($event) => {
                  item.onKeyPress && item.onKeyPress($event);
                }
              " clearable :autosize="{
                minRows: item.minRows || 2,
                maxRows: item.maxRows || 10,
              }" :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " :ref="item.field" />
          <Input class="input-with-select" clearable v-else-if="item.type == 'password'" type="password" autocomplete="off" v-model.number="_formFields[item.field]" @on-keypress="
                ($event) => {
                  item.onKeyPress && item.onKeyPress($event);
                }
              " :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " :ref="item.field" />
          <div v-else-if="item.type == 'textSpanCheck'">
            <el-checkbox v-model="_formFields[item.field]"></el-checkbox>
            <span class="male">{{item.cont[0]}}</span>
            <Input style="width: 60px" v-model="_formFields[item.field1]" type="text" @on-keypress="
                  ($event) => {
                    item.onKeyPress && item.onKeyPress($event);
                  }
                " />
            <span>{{item.cont[1]}} {{item.cont[2]}}</span>
            <Input style="width: 60px" v-model="_formFields[item.field2]" type="text" @on-keypress="
                  ($event) => {
                    item.onKeyPress && item.onKeyPress($event);
                  }
                " />
            <span>{{item.cont[3]}}</span>
          </div>
          <div v-else-if="item.type == 'textSpan'">
            <span>{{item.cont[0]}}</span>
            <Input style="width: 50px" v-model="_formFields[item.field]" type="text" @on-keypress="
                  ($event) => {
                    item.onKeyPress && item.onKeyPress($event);
                  }
                " clearable :ref="item.field" />
            <span>{{item.cont[1]}}</span>
          </div>
          <Input v-else-if="item.type == 'textAppend'" v-model="_formFields[item.field]" :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " type="text" @on-keypress="
                  ($event) => {
                    item.onKeyPress && item.onKeyPress($event);
                  }
                " :ref="item.field">
          <template slot="append">{{item.cont}}</template>
          </Input>
          <!-- 复合型输入框 -->
          <Input class="intSelet" clearable v-else-if="item.type == 'intSel'" @on-keypress="
                ($event) => {
                  item.onKeyPress && item.onKeyPress($event);
                }
              " @input="
                ($event) => {
                  item.onInput && item.onInput($event);
                }
              " @on-blur="onBlur(item, _formFields[item.field])" v-model="_formFields[item.field]" :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " :ref="item.field">
          <Select v-model="_formFields[item.field2]" clearable filterable slot="prepend" placeholder="请选择">
            <Option v-for="(kv, kvIndex) in item.data" :key="kvIndex" :value="kv.key" v-show="!kv.hidden">{{ kv.value }}</Option>
          </Select>
          </Input>
          <Input clearable v-else @on-keypress="
                ($event) => {
                  item.onKeyPress && item.onKeyPress($event);
                }
              " @input="
                ($event) => {
                  item.onInput && item.onInput($event);
                }
              " @on-blur="onBlur(item, _formFields[item.field])" v-model="_formFields[item.field]" :placeholder="
                item.placeholder ? item.placeholder : '请输入' + item.title
              " :ref="item.field" />

          <div class="form-extra" v-if="item.extra">
            <form-expand v-if="item.extra.render" :render="item.extra.render"></form-expand>
            <el-tooltip effect="dark" placement="top" v-if="item.extra.tooltip">
              <div slot="content" v-html="item.extra.content"></div>
              <i class="el-icon-question" />
            </el-tooltip>
            <a v-else :style="item.extra.style" @click="
                  () => {
                    item.extra.click &&
                      item.extra.click(item, _formFields[item.field]);
                  }
                ">
              <Icon v-if="item.extra.icon" :type="item.extra.icon" />
              {{ item.extra.text }}
            </a>
          </div>
        </div>
      </FormItem>
      </Col>
    </Row>
    <slot name="footer"></slot>
  </Form>
</template>
<script>
import moment from 'moment'
import FormExpand from './VolForm/VolFormRender'
export default {
  components: {
    FormExpand,
    VolUpload: () => import('@/components/basic/VolUpload.vue'),
    KindEditor: () => import('@/components/kindeditor/KindEditor.vue'),
    VolUploadUpgrade: () => import('@/components/basic/VolUploadUpgrade.vue'),
  },
  props: {
    loadKey: {
      // 是否加载formRules字段配置的数据源
      type: Boolean,
      default: false,
    },
    width: {
      // 表单宽度
      type: Number,
      default: 0,
    },
    labelWidth: {
      // 表单左边label文字标签的宽度
      type: Number,
      default: 100,
    },
    formRules: {
      // 表单配置规则，如字段类型，是否必填
      type: Array,
      default: [],
    },
    formFileds: {
      // 表单字段
      type: Object,
      default: () => {
        return {}
      },
    },
    formFields: {
      // 2020.09.13增加formFileds拼写错误兼容处理
      // 表单字段
      type: Object,
      default: () => {
        return {}
      },
    },
    editor: {
      // 2021.01.16编辑器信息 {uploadImgUrl:"",upload:null//上传方法}
      type: Object,
      default: () => {
        return {}
      },
    },
  },
  watch: {},
  created() {
    // 2020.09.13增加formFileds拼写错误兼容处理
    this._formFields = Object.keys(this.formFields).length ? this.formFields : this.formFileds
    this.initFormRules(true)
  },
  data() {
    return {
      _formFields: {},
      remoteCall: true,
      errorImg: 'this.src="' + require('@/assets/imgs/error-img.png') + '"',
      rule: {
        change: ['checkbox', 'select', 'selectList', 'date', 'datetime', 'drop', 'radio', 'cascader','cascaderEl'], // 2020.05.31增加级联类型
        phone: /^[1][3,4,5,6,7,8,9][0-9]{9}$/,
        telephone: /^(\(\d{3,4}\)|\d{3,4}-|\s)?\d{7,14}$/, //电话
        // decimal: /(^[\-0-9][0-9]*([.][0-9]{0,2})?)$/, //两位小数
        decimal: /^\d+(?:\.\d{1,2})?$/, // 两位小数
        alphanumeric: /^\w+$/, //数字  字母
        telephones: /^1\d{10}$|^(0\d{2,3}-?|\(0\d{2,3}\))?[1-9]\d{4,7}(-\d{1,8})?$/,
        // notnumbers:/^1\d{10}$|^(0\d{2,3}-?|\(0\d{2,3}\))?[1-9]\d{4,7}(-\d{1,8})?$/,
        notnumbers: /^(?!(\d+)$)[\u4e00-\u9fffa-zA-Z\d\-_]+$/,

        // decimal: /^(([1-9]{1}\\d*)|([0]{1}))(\\.(\\d){0,2})?$/,//原本的小数验证
        number: /(^[\-0-9][0-9]*([0-9]+)?)$/,
        minusDecimal: /^([\+ \-]?(([1-9]\d*)|(0)))([.][0-9]{0,2})?$/, //正负两位小数
        ZDecimal: /^[0-9]+(.[0-9]{1,2})?$/, //正两位小数
        capitalization: /[^A-Z].[^A-Z]/,
        email: /^[A-Za-z0-9+_.-]+@(.+)$/,
      },
      inputTypeArr: ['text', 'string', 'mail', 'textarea', 'password'],
      types: {
        int: 'number',
        byte: 'number',
        decimal: 'number', // "float",
        minusDecimal: 'number', // 正负数,
        ZDecimal: 'number',
        alphanumeric: 'string', //数字和字母
        string: 'string',
        bool: 'boolean',
        date: 'datetime',
        time: 'time',
        date: 'date',
        mail: 'email',
      },
      span: 0,
      ruleValidate: {},
      rangeFields: [],
    }
  },
  methods: {
    // 判断是否是特定的需求 一级下面有二级一级不可选中
    changeProducts(value, selectedData, listData, CascaderValue) {
      if (selectedData.length == 1) {
        listData.forEach((_) => {
          // if (selectedData[0].id == _.id && _.children.length) {
          if (selectedData[0].id == _.id) {
            this._formFields[CascaderValue] = []
            return false
          } else {
            return true
          }
        })
      } else {
        return true
      }
    },
    // 2021.01.30增加日期自定义格式
    getDateFormat(item) {
      if (item.format) {
        console.log(format, 'format')
        return format
      }
      if (item.type == 'month') {
        return undefined
      }
      if (item.type == 'date1') {
        console.log(item.type, 'date1')
        return 'yyyy-MM-dd'
      }
      return item.type == 'date' ? 'yyyy-MM-dd' : 'yyyy-MM-dd HH:mm:ss'
    },

    previewImg(url) {
      this.base.previewImg(url, this.http.ipAddress)
    },
    getSrc(path) {
      if (!path) return
      if (!this.base.isUrl(path) && path.indexOf('.') != -1) {
        let filePath = path.indexOf('https://oss.i-town.cn/itown') != -1 ? path : (path.indexOf('https://') != -1 ? path : (this.http.ipAddress + path))
        return filePath
      }
      return path
    },
    // 是否为图片文件等格式并对字段的转换成数组：[{name:'1.jpg',path:'127.0.0.1/ff/1.jpg'}]
    isFile(item, _formFields) {
      if (item.type == 'img' || item.columnType == 'img' || item.type == 'excel' || item.type == 'file') {
        this.convertFileToArray(item, _formFields)
        return true
      }
      return false
    },
    isReadonlyImgFile(item, _formFields) {
      if ((item.disabled || item.readonly) && this.isFile(item, _formFields)) {
        return true
      }
      return false
    },
    convertFileToArray(item, _formFields) {
      if (!item.maxFile) {
        item.maxFile = 1 // 默认只能上传一个文件，可以在onInit中设置
      }

      let fileInfo = _formFields[item.field]
      if (fileInfo instanceof Array) {
        fileInfo.forEach((x) => {
          if (x.hasOwnProperty('path')) {
            if (x.path && !this.base.isUrl(x.path)) {
              // 这里修改后死循环?
              // x.path = this.http.ipAddress + x.path;
            }
          }
        })
        return
      }
      if (fileInfo === null || fileInfo === undefined) {
        _formFields[item.field] = []
        return
      }
      // 将以逗号隔开的文件分割成数组127.0.0.1/aa/1.jpg,将127.0.0.1/aa/2.jpg
      if (typeof fileInfo === 'string') {
        if (fileInfo.trim() === '') {
          _formFields[item.field] = []
          return
        }
        // 如果文件路径是字符串，则使用，拆分
        fileInfo = fileInfo.replace(/\\/g, '/')
        let files = fileInfo.split(',')
        _formFields[item.field] = []
        for (let index = 0; index < files.length; index++) {
          let file = files[index]
          let splitFile = file.split('/')
          _formFields[item.field].push({
            name: splitFile.length > 0 ? splitFile[splitFile.length - 1] : file,
            path: file, // this.base.isUrl(file) ? file : this.http.ipAddress + file,
          })
        }
      }
    },
    dowloadFile(file) {
      this.base.dowloadFile(
        file.path,
        file.name,
        {
          Authorization: this.$store.getters.getToken(),
        },
        this.http.ipAddress
      )
    },
    validatorPhone(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.phone.test((value || '').trim())) {
        return callback(new Error('请输入正确的手机号'))
      }
      callback()
    },
    // 验证电话
    validatorTelephone(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.telephone.test((value || '').trim())) {
        return callback(new Error('请输入正确的电话号码'))
      }
      callback()
    },
    // 验证邮箱
    validatorTeleEmail(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.email.test((value || '').trim())) {
        return callback(new Error('请输入正确的邮箱'))
      }
      callback()
    },
    // 电话号码和手机号
    validatorTelephones(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.telephones.test((value || '').trim())) {
        return callback(new Error('请输入正确的联系方式'))
      }
      callback()
    },
    // input不能输入纯数字 notnumbers
    validatorNotnumbers(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.notnumbers.test((value || '').trim())) {
        return callback(new Error('请输入正确的格式,不能输入纯数字'))
      }
      callback()
    },
    validatorPwd(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if ((value + '').trim().length < 6) {
        return callback(new Error('密码长度不能小于6位'))
      }
      callback()
    },
    // 验证数字和字母
    validatorAlphanumeric(rule, value, callback) {
      if (!rule.required && !value && value != '0') {
        return callback()
      }
      if (!this.rule.alphanumeric.test((value || '').trim())) {
        return callback(new Error('请输入数字和字母'))
      }
      callback()
    },
    convertArrayValue(data, val) {
      // 2020.12.13增加表单多选只转换字典
      // 编辑多选table显示
      let valArr = val instanceof Array ? val : val.split(',')
      for (let index = 0; index < valArr.length; index++) {
        var _item = data.find((x) => {
          return x.key && x.key != '0' && x.key + '' == valArr[index] + ''
        })
        if (_item) {
          valArr[index] = _item.value
        }
      }
      return valArr.join(',')
    },
    getText(_formFields, item) {
      // 2019.10.24修复表单select组件为只读的属性时没有绑定数据源
      let text = _formFields[item.field]
      if (typeof text === 'function') return text(_formFields)
      if (text === 'null' || text === '' || text === null || text === undefined) return '--'
      //2021.03.02增加只读时日期处理
      if (item.type == 'date' || item.type == 'date1') {
        return text.replace('T', ' ').split(' ')[0]
      }
      //2021.03.31修复表单switch只读时没有转换值的问题
      if (item.type == 'switch') {
        return text ? '是' : '否'
      }
      if (!item.data) return text
      if (item.type == 'selectList' || item.type == 'checkbox') {
        return this.convertArrayValue(item.data, text)
      }
      var _item = item.data.find((x) => {
        return x.key == text
      })
      if(item.type == "cascaderEl") {
        const getSelectedNames = (ids, options) => {
          let names = []
          const findNames = (ids, options, parentId = '', parentName = '') => {
            options.forEach(node => {
              node.curId = parentId + (parentId ? '/' : '') + node.value
              node.curAllName = parentName + (parentName ? '/' : '') + node.label
              if (ids.includes(node.value)) {
                names.push(node.curAllName)
              }
              if (node.children && node.children.length) {
                findNames(ids, node.children, node.curId, node.curAllName);
              }
            });
          };
          findNames(ids, options);
          return names;
        }
        let va = getSelectedNames(_formFields[item.field], item.data)
        return va.length ? va.join() : ''
      }
      return _item ? _item.value : text
    },
    onClear(item, _formFields) {
      // 远程select标签清空选项
      item.data.splice(0)
      // console.log(2);
    },
    onChange(item, value) {
      if (item.onChange && typeof item.onChange === 'function') {
        item.onChange(value, item)
      }
    },
    onBlur(item, value) {
      if (item.onBlur && typeof item.onBlur === 'function') {
        item.onBlur(value, item)
      }
    },
    onRemoteChange(item, value) {
      // 第二次打开时，默认值成了undefined，待查viewgrid中重置代码
      if (value == undefined && item.data.length > 0) {
        this._formFields[item.field] = item.data[0].key
        //  console.log('undefined');
      }
      this.remoteCall = false
      if (item.onChange && typeof item.onChange === 'function') {
        item.onChange(value, item)
      }
    },
    getData(item) {
      return item.data
    },
    initSource() {
      let keys = [],
        binds = []
      // 初始化字典数据源
      this.formRules.forEach((item) => {
        item.forEach((x) => {
          if (x.dataKey && (!x.data || x.data.length == 0) && !x.remote) {
            // if (!x.data)
            x.data = []
            binds.push({ key: x.dataKey, data: x.data })
            if (keys.indexOf(x.dataKey) == -1) {
              keys.push(x.dataKey)
            }
          }
        })
      })

      if (keys.length == 0) return

      this.http.post('/api/Dictionary/GetVueDictionary', keys).then((dic) => {
        this.bindOptions(dic, binds)
      })
    },
    // 远程搜索(打开弹出框时应该禁止搜索)
    remoteSearch(item, _formFields, val) {
      if (val == '' || (item.data.length == 1 && (val == item.data[0].key || val == item.data[0].value))) {
        return
      }
      // 弹出框或初始化表单时给data设置数组默认值2
      // 2020.09.26修复远程搜索自定义url不起作用的问题
      let url
      if (typeof item.url === 'function') {
        url = item.url(val, item.dataKey, item)
      } else {
        url = (item.url || '/api/Dictionary/GetSearchDictionary') + '?dicNo=' + item.dataKey + '&value=' + val
      }
      this.http.post(url).then((dicData) => {
        this.$set(item, 'loading', false)
        item.data = dicData
        this.formRules[item.point.x].splice(item.point.y, 1, item)
      })
    },
    bindOptions(dic, binds) {
      dic.forEach((d) => {
        binds.forEach((x) => {
          if (x.key != d.dicNo) return true
          // 如果有数据的则不查询
          if (x.data.length > 0) return true
          if (d.data.length > 0 && !d.data[0].hasOwnProperty('key')) {
            let source = d.data,
              newSource = new Array(source.length)
            for (let index = 0; index < source.length; index++) {
              newSource[index] = {
                key: source['key'] + '',
                value: source['value'],
              }
            }
            x.data.push(...newSource)
          } else {
            x.data.push(...d.data)
          }
        })
      })
    },
    getObject(date) {
      if (typeof date === 'object') {
        return date
      }
      return new Date(date)
    },
    validateNumber() {},
    formatTime(time) {
      return moment(time).format('YYYY-MM-DD')
    },
    changeTime(time) {
      // console.log(time);
      return time + ''
    },
    reset(sourceObj) {
      // 重置表单时，禁用远程查询
      this.$refs['formValidate'].resetFields()
      if (this.rangeFields.length) {
        this.rangeFields.forEach((key) => {
          this._formFields[key].splice(0)
          this._formFields[key] = [null, null]
        })
      }
      if (!sourceObj) return
      for (const key in this._formFields) {
        if (sourceObj.hasOwnProperty(key)) {
          this._formFields[key] = sourceObj[key]
        }
      }
      //  this.remoteCall = true;
    },
    validate(callback) {
      let result = true
      this.$refs['formValidate'].validate((valid) => {
        if (!valid) {
          this.$Message.error('数据验证未通过!')
          result = false
        } else if (typeof callback === 'function') {
          callback(valid)
        }
      })
      return result
    },
    initUpload(item, init) {
      if (!init) return
      if (item.type == 'img' || item.columnType == 'img' || item.type == 'excel' || item.type == 'file') {
        // 只是没设置是否自动上传的，默认都是选择文件后自动上传
        if (!item.hasOwnProperty('autoUpload')) {
          item.autoUpload = true
        }
        if (!item.hasOwnProperty('fileList')) {
          item.fileList = true
        }
        if (!item.hasOwnProperty('downLoad')) {
          item.downLoad = true
        }
        if (!item.removeBefore) {
          item.removeBefore = (index, file, files) => {
            return true
          }
        }
        if (!item.fileClick) {
          item.fileClick = (index, file, files) => {
            return true
          }
        }
        if (!item.onChange) {
          item.onChange = (files) => {
            return true
          }
        }
        if (!item.uploadAfter) {
          item.uploadAfter = (result, files) => {
            return true
          }
        }
        if (!item.uploadBefore) {
          //  console.log("111");
          item.uploadBefore = (files) => {
            return true
          }
        }
      }
    },
    initFormRules(init) {
      if (this.loadKey) {
        this.initSource()
      }
      //  this.ruleValidate={};
      this.formRules.forEach((row, xIndex) => {
        if (row.length > this.span) this.span = row.length

        row.forEach((item, yIndex) => {
          // 目前只支持select单选远程搜索，remote远程从后台字典数据源进行搜索，url从指定的url搜索
          if (item.remote || item.url) {
            // item.remoteData = [];
            item.loading = false
            item.point = { x: xIndex, y: yIndex }
          }
          // 初始化上传文件信息
          this.initUpload(item, init)
          // 初始化数据源空对象
          if (item.dataKey) {
            // 下拉框都强制设置为字符串类型
            item.columnType = 'string'
            if (!item.data) {
              item.data = []
            }
          }
          if (item.range || item.type == 'range') {
            if (!(this._formFields[item.field] instanceof Array) || this._formFields[item.field].length != 2) {
              // this._formFields[item.field] = [null, null]
              this._formFields[item.field] = []
            }
            this.rangeFields.push(item.field)
          }
        })
      })
    },
    getRule(item, _formFields) {
      //console.log('item',item)
      //2021.07.17增加只读表单不验证

      if (item.readonly || item.disabled) return
      // 用户设置的自定义方法
      if (item.validator && typeof item.validator === 'function') {
        return {
          validator: (rule, val, callback) => {
            // 用户自定义的方法，如果返回了值，直接显示返回的值，验证不通过
            let message = item.validator(rule, val)
            if (message) return callback(new Error(message + ''))
            return callback()
          },
          required: item.required,
          trigger: this.rule.change.indexOf(item.type) != -1 ? 'change' : 'blur',
        }
      }

      // 设置数字的最大值民最小值
      if (
        item.type == 'number' ||
        item.columnType == 'number' ||
        item.columnType == 'int' ||
        item.type == 'decimal' ||
        item.type == 'minusDecimal' ||
        item.type == 'ZDecimal' ||
        item.type == 'capitalization'
      ) {
        // 如果是必填项的数字，设置一个默认最大与最值小
        if (item.required && item.type == 'minusDecimal') {
        } else if (item.required && typeof item.min !== 'number') {
          item.min = item.type == 'decimal' ? 0.01 : 1
        } else if (item.required && item.type == 'ZDecimal') {
        } else if (item.required && item.type == 'capitalization') {
        }

        return {
          required: item.required,
          message: item.title,
          title: item.title,
          trigger: 'blur',
          min: item.min,
          max: item.max,
          type: item.columnType || item.type,
          validator: (rule, value, callback) => {

            if (!rule.min && !rule.max) {
              if (rule.required) {
                if (value == '') {
                  _formFields[rule.field] = 0
                  return callback()
                }
              }
              if (value === '' || value === undefined) return callback()
            }
            if (rule.type == 'number') {
              if (!this.rule.number.test(value)) {
                rule.message = rule.title + '只能是整数'
                return callback(new Error(rule.message))
              }
            } else if (rule.type == 'decimal') {
              if (value) {
                if (!this.rule.decimal.test(value)) {
                  rule.message = rule.title + '只能是数字（两位小数）'
                  return callback(new Error(rule.message))
                }
              }
            } else if (rule.type == 'minusDecimal') {
              if (!this.rule.minusDecimal.test(value)) {
                rule.message = rule.title + '只能是正负数字（两位小数）'
                return callback(new Error(rule.message))
              }
            } else if (rule.type == 'ZDecimal') {
              if (!this.rule.ZDecimal.test(value)) {
                rule.message = rule.title + '只能是正数字（两位小数）'
                return callback(new Error(rule.message))
              }
            } else if (rule.type == 'capitalization') {
              if (!this.rule.capitalization.test(value)) {
                rule.message = rule.title + '只能是英文字母'
                return callback(new Error(rule.message))
              }
            }

            //  else {
            //   if (value) {
            //     if (!this.rule.alphanumeric.test(value)) {
            //       rule.message = rule.title + "只能数字和字母";
            //       return callback(new Error(rule.message));
            //     }
            //   }
            // }
            if (rule.min !== undefined && typeof rule.min === 'number' && value < rule.min) {
              rule.message = rule.title + '不能小于' + rule.min
              return callback(new Error(rule.message))
            }
            if (rule.max !== undefined && typeof rule.max === 'number' && value > rule.max) {
              rule.message = rule.title + '不能大于' + rule.max
              return callback(new Error(rule.message))
            }
            return callback()
          },
        }
      }

      // 手机、密码验证
      if (item.type == 'password' || item.type == 'phone' || item.type == 'telephone' || item.type == 'telephones' || item.type == 'notnumbers') {
        // validatorNotnumbers
        return {
          validator:
            item.type == 'phone'
              ? this.validatorPhone
              : item.type == 'telephone'
              ? this.validatorTelephone
              : item.type == 'telephones'
              ? this.validatorTelephones
              : item.type == 'notnumbers'
              ? this.validatorNotnumbers
              : this.validatorPwd,
          required: item.required,
          trigger: 'blur',
        }
      }
      // 邮箱验证
      if (item.type == 'mail' || item.type == 'email') {
        console.log(item)
        return {
          validator: this.validatorTeleEmail,
          required: item.required,
          trigger: 'blur',
        }
      }
      // 字母数字验证
      if (item.type == 'alphanumeric') {
        return {
          validator: this.validatorAlphanumeric,
          required: item.required,
          trigger: 'blur',
        }
      }
      if(item.type=="img"||item.type=="imgupgrade"){
        if (_formFields[item.field] == null) {
          _formFields[item.field] = []
        }
        // if(_formFields[item.field]!=""&&_formFields[item.field]!=null){
        if(_formFields[item.field].length>0){
          this.$nextTick(()=>{
            this.$refs['formValidate'].validateField(item.field)
          })
        }
        return {
          required: item.required,
          message: '请上传' + item.title,
          trigger: 'change',
          validator: (rule, val, callback) => {
            if (val.length == 0&&item.required ) {
              return callback(new Error())
            }else{
              return callback()
            }
          },
        }
      // }
      }




      if (!item.required && item.type != 'mail') {
        return {
          required: false,
        }
      }

      if (!item.hasOwnProperty('type')) {
        item.type = 'text'
      }

      // inputTypeArr:['text','string','mail','textarea'],
      if (this.inputTypeArr.indexOf(item.type) != -1) {
        let message = item.title + (item.type == 'mail' ? '必须是一个邮箱地址' : '不能为空')
        let type = item.type == 'mail' ? 'email' : this.types[item.columnType]
        let _rule = {
          required: true,
          message: message,
          trigger: 'blur',
          type: type,
        }
        if (item.type == 'mail') {
          _rule.required = item.required
          return [
            _rule,
            {
              type: type,
              message: message,
              trigger: 'blur',
            },
          ]
        }
        if (item.min) {
          _rule.min = item.min
          _rule.message = item.title + '至少' + item.min + '个字符!'
        }
        if (item.max) {
          return [
            _rule,
            {
              max: item.max,
              required: true,
              message: item.title + '最多' + item.max + '个字符!',
              trigger: 'blur',
            },
          ]
        }
        return _rule
      }

      if (item.type == 'radio') {
        return {
          required: item.required,
          message: '请选择' + item.title,
          trigger: 'change',
          type: 'string',
          validator: (rule, value, callback) => {
            if (value == undefined || value === '') {
              return callback(new Error(rule.message))
            }
            return callback()
          }
        }
      }
      if (item.type == 'date' || item.type == 'datetime' || item.type == 'time') {
        return {
          required: true,
          message: '请选择' + item.title,
          trigger: 'change',
          type: item.range ? 'array' : 'string',
          validator: (rule, val, callback) => {
            // 用户自定义的方法，如果返回了值，直接显示返回的值，验证不通过
            if (!val || (item.range && val.length == 0)) {
              return callback(new Error('请选择日期'))
            } else if (item.range && (val[0] == '' || val[0] == null)) {
              return callback(new Error('请选择日期'))
            }
            // if (message) return callback(new Error(message + ""));
            return callback()
          },
        }
      }

      if (
        item.type == 'select' ||
        item.type == 'selectList' ||
        item.type == 'checkbox' ||
        item.type == 'drop' ||
        item.type == 'cascader'||
        item.type == 'cascaderEl' // 2020.05.31增加级联类型
      ) {
        let _rule = {
          required: true,
          message: '请选择' + item.title,
          min: item.min || 1,
          type: 'array',
          trigger: 'change',
          type: this.types[item.columnType],
          validator: (rule, value, callback) => {
            if (value == undefined || value === '' || value.length == 0) {
              return callback(new Error(rule.message))
            }
            return callback()
          },
        }

        if (!item.max) return _rule
        return [
          _rule,
          {
            message: '最多只能选择' + item.max + '项' + item.title,
            max: item.max,
            type: 'array',
            trigger: 'change',
          },
        ]
      }
      return {
        required: false,
      }
    },
    validateField(item, callback) {
      // 2020.07.17增加对日期onchange时校验
      let fields = this.$refs.formValidate.fields
      fields.forEach((field) => {
        if (field.prop == item.field) {
          field.validate('', (error) => {
            // console.log(error);
          })
        }
      })
      // 2020.07.24增加日期onChange事件
      item.onChange && item.onChange(this._formFields[item.field])
    },
    getDateOptions(item) {
      //2021.07.17设置时间可选范围
      if (item.min || item.max) {
        return {
          disabledDate: (date) => {
            if (!date) return true
            return (
              date.valueOf() < (typeof item.min == 'number' ? item.min : new Date(item.min || '1970-01-01').valueOf()) ||
              date.valueOf() > (typeof item.max == 'number' ? item.max : new Date(item.max || '2100-01-01').valueOf())
            )
          },
        }
      }
    },
  },
}
</script>
<style>
.ivu-date-picker {
  width: 100%;
}
/* .ivu-form-item {
  margin-bottom: 20px !important;
} */
</style>
<style scoped>
.readonly-input >>> input {
  box-shadow: none;
  border: 0px;
}
.line-row >>> .ivu-select .ivu-select-dropdown {
  width: 100% !important;
  z-index: 99999;
}

.line-row >>> .ivu-form-item img {
  max-height: 100px;
}
/* .ivu-form-item{

} */
.line-row >>> .ivu-form-item-label {
  overflow: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
}
.intSelet >>> .ivu-select {
  width: 200px !important;
}
.intSelet >>> .ivu-select .ivu-select-dropdown {
  width: 200px !important;
}
</style>
<style lang="less" scoped>
.form-imgs {
  display: inline-block;
  .img-item {
    position: relative;
    cursor: pointer;
    margin: 0 10px 10px 0;
    float: left;
    height: 100px;
    border: 1px solid #9e9e9e;
    overflow: hidden;
    border-radius: 5px;
    width: 100px;
  }
  img {
    margin: 0;
    padding: 0;
    width: 100%;
    height: 100%;
    object-fit: cover;
  }
}
.form-item-extra {
  display: flex;
  > div:first-child {
    flex: 1;
  }
  .form-extra {
    margin-left: 10px;
  }
}
.male {
  margin-left: 10px;
}
.el-tooltip {
  width: 50%;
}
</style>
